﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Security.Cryptography;
using System.Web;
using System.IO;

using System.Net;

namespace TicketsPhone.Domain.Utils
{
    public class Utilidades
    {

        /// <summary>
        /// Genera una cadena encriptada en MD5
        /// </summary>
        /// <param name="input">valor que se desea encriptar</param>
        /// <returns>cadena encriptada en md5</returns>
        public static string MD5(string input)
        {
            MD5CryptoServiceProvider x = new System.Security.Cryptography.MD5CryptoServiceProvider();
            byte[] bs = System.Text.Encoding.UTF8.GetBytes(input);
            bs = x.ComputeHash(bs);
            System.Text.StringBuilder s = new System.Text.StringBuilder();
            foreach (byte b in bs)
            {
                s.Append(b.ToString("x2").ToLower());
            }
            string password = s.ToString();
            return password;
        }

        

        


        

        ///// <summary>
        ///// Renderiza un control y lo convierte en html
        ///// </summary>
        ///// <param name="ctrl">Control que se quiere renderizar</param>
        ///// <returns>string con el html que genera el control</returns>
        //public static string RenderControl(Control ctrl)
        //{
        //    try
        //    {
        //        StringBuilder sb = new StringBuilder();
        //        StringWriter tw = new StringWriter(sb);
        //        HtmlTextWriter hw = new HtmlTextWriter(tw);

        //        ctrl.RenderControl(hw);
        //        return sb.ToString();
        //    }
        //    catch (Exception ex)
        //    {
        //        throw ex;
        //    }
        //}

        //public static string RenderView(
        //      ControllerContext controllerContext,
        //      string viewPath,
        //      string masterPath,
        //      ViewDataDictionary viewData,
        //      TempDataDictionary tempData)
        //{
        //    Stream filter = null;
        //    ViewUserControl viewPage = new ViewUserControl();

        //    TextWriter tw = TextWriter.Null;

        //    //Right, create our view
        //    viewPage.ViewContext = new ViewContext(controllerContext, new WebFormView(controllerContext, viewPath, masterPath), viewData, tempData, tw);

        //    //Get the response context, flush it and get the response filter.
        //    var response = viewPage.ViewContext.HttpContext.Response;
        //    response.Flush();
        //    var oldFilter = response.Filter;

        //    try
        //    {
        //        //Put a new filter into the response
        //        filter = new MemoryStream();
        //        response.Filter = filter;

        //        //Now render the view into the memorystream and flush the response
        //        viewPage.ViewContext.View.Render(viewPage.ViewContext, viewPage.ViewContext.HttpContext.Response.Output);
        //        response.Flush();

        //        //Now read the rendered view.
        //        filter.Position = 0;
        //        var reader = new StreamReader(filter, response.ContentEncoding);
        //        return reader.ReadToEnd();
        //    }
        //    finally
        //    {
        //        //Clean up.
        //        if (filter != null)
        //        {
        //            filter.Dispose();
        //        }

        //        //Now replace the response filter
        //        response.Filter = oldFilter;
        //    }
        //}

        /// <summary>
        /// Retorna el HTML generado por un HttpRequest
        /// </summary>
        /// <returns>url solicitada</returns>
        public static string ObtenerHttpRequest(string url)
        {
            // Create a request using a URL that can receive a post. 
            WebRequest request = WebRequest.Create(url);
            // Set the Method property of the request to POST.
            request.Method = "GET";

            Stream dataStream = request.GetRequestStream();

            WebResponse response = request.GetResponse();
            // Display the status.
            Console.WriteLine(((HttpWebResponse)response).StatusDescription);
            // Get the stream containing content returned by the server.
            dataStream = response.GetResponseStream();
            // Open the stream using a StreamReader for easy access.
            StreamReader reader = new StreamReader(dataStream);
            // Read the content.
            string responseFromServer = reader.ReadToEnd();
            // Display the content.
            Console.WriteLine(responseFromServer);
            //Response.Write(responseFromServer);
            // Clean up the streams.
            reader.Close();
            dataStream.Close();
            response.Close();

            return responseFromServer;
        }

        /// <summary>
        /// Genera una clave aleatoria, con un minimo y máximo de caracteres
        /// </summary>
        /// <param name="minLength">Minimo de caracteres para la clave</param>
        /// <param name="maxLength">Máximo de caracteres para la clave</param>
        /// <returns>Clave generada</returns>
        public static String GenerarClave(int minLength, int maxLength)
        {

            // Define supported password characters divided into groups.
            // You can add (or remove) characters to (from) these groups.
            string PASSWORD_CHARS_LCASE = "abcdefgijkmnopqrstwxyz";
            string PASSWORD_CHARS_UCASE = "ABCDEFGHJKLMNPQRSTWXYZ";
            string PASSWORD_CHARS_NUMERIC = "23456789";

            // Make sure that input parameters are valid.
            if (minLength <= 0 || maxLength <= 0 || minLength > maxLength)
                return null;

            // Create a local array containing supported password characters
            // grouped by types. You can remove character groups from this
            // array, but doing so will weaken the password strength.
            char[][] charGroups = new char[][] 
            {
                PASSWORD_CHARS_LCASE.ToCharArray(),
                PASSWORD_CHARS_UCASE.ToCharArray(),
                PASSWORD_CHARS_NUMERIC.ToCharArray()
            };

            // Use this array to track the number of unused characters in each
            // character group.
            int[] charsLeftInGroup = new int[charGroups.Length];

            // Initially, all characters in each group are not used.
            for (int i = 0; i < charsLeftInGroup.Length; i++)
                charsLeftInGroup[i] = charGroups[i].Length;

            // Use this array to track (iterate through) unused character groups.
            int[] leftGroupsOrder = new int[charGroups.Length];

            // Initially, all character groups are not used.
            for (int i = 0; i < leftGroupsOrder.Length; i++)
                leftGroupsOrder[i] = i;

            // Because we cannot use the default randomizer, which is based on the
            // current time (it will produce the same "random" number within a
            // second), we will use a random number generator to seed the
            // randomizer.

            // Use a 4-byte array to fill it with random bytes and convert it then
            // to an integer value.
            byte[] randomBytes = new byte[4];

            // Generate 4 random bytes.
            RNGCryptoServiceProvider rng = new RNGCryptoServiceProvider();
            rng.GetBytes(randomBytes);

            // Convert 4 bytes into a 32-bit integer value.
            int seed = (randomBytes[0] & 0x7f) << 24 |
                        randomBytes[1] << 16 |
                        randomBytes[2] << 8 |
                        randomBytes[3];

            // Now, this is real randomization.
            Random random = new Random(seed);

            // This array will hold password characters.
            char[] password = null;

            // Allocate appropriate memory for the password.
            if (minLength < maxLength)
                password = new char[random.Next(minLength, maxLength + 1)];
            else
                password = new char[minLength];

            // Index of the next character to be added to password.
            int nextCharIdx;

            // Index of the next character group to be processed.
            int nextGroupIdx;

            // Index which will be used to track not processed character groups.
            int nextLeftGroupsOrderIdx;

            // Index of the last non-processed character in a group.
            int lastCharIdx;

            // Index of the last non-processed group.
            int lastLeftGroupsOrderIdx = leftGroupsOrder.Length - 1;

            // Generate password characters one at a time.
            for (int i = 0; i < password.Length; i++)
            {
                // If only one character group remained unprocessed, process it;
                // otherwise, pick a random character group from the unprocessed
                // group list. To allow a special character to appear in the
                // first position, increment the second parameter of the Next
                // function call by one, i.e. lastLeftGroupsOrderIdx + 1.
                if (lastLeftGroupsOrderIdx == 0)
                    nextLeftGroupsOrderIdx = 0;
                else
                    nextLeftGroupsOrderIdx = random.Next(0,
                                                         lastLeftGroupsOrderIdx);

                // Get the actual index of the character group, from which we will
                // pick the next character.
                nextGroupIdx = leftGroupsOrder[nextLeftGroupsOrderIdx];

                // Get the index of the last unprocessed characters in this group.
                lastCharIdx = charsLeftInGroup[nextGroupIdx] - 1;

                // If only one unprocessed character is left, pick it; otherwise,
                // get a random character from the unused character list.
                if (lastCharIdx == 0)
                    nextCharIdx = 0;
                else
                    nextCharIdx = random.Next(0, lastCharIdx + 1);

                // Add this character to the password.
                password[i] = charGroups[nextGroupIdx][nextCharIdx];

                // If we processed the last character in this group, start over.
                if (lastCharIdx == 0)
                    charsLeftInGroup[nextGroupIdx] =
                                              charGroups[nextGroupIdx].Length;
                // There are more unprocessed characters left.
                else
                {
                    // Swap processed character with the last unprocessed character
                    // so that we don't pick it until we process all characters in
                    // this group.
                    if (lastCharIdx != nextCharIdx)
                    {
                        char temp = charGroups[nextGroupIdx][lastCharIdx];
                        charGroups[nextGroupIdx][lastCharIdx] =
                                    charGroups[nextGroupIdx][nextCharIdx];
                        charGroups[nextGroupIdx][nextCharIdx] = temp;
                    }
                    // Decrement the number of unprocessed characters in
                    // this group.
                    charsLeftInGroup[nextGroupIdx]--;
                }

                // If we processed the last group, start all over.
                if (lastLeftGroupsOrderIdx == 0)
                    lastLeftGroupsOrderIdx = leftGroupsOrder.Length - 1;
                // There are more unprocessed groups left.
                else
                {
                    // Swap processed group with the last unprocessed group
                    // so that we don't pick it until we process all groups.
                    if (lastLeftGroupsOrderIdx != nextLeftGroupsOrderIdx)
                    {
                        int temp = leftGroupsOrder[lastLeftGroupsOrderIdx];
                        leftGroupsOrder[lastLeftGroupsOrderIdx] =
                                    leftGroupsOrder[nextLeftGroupsOrderIdx];
                        leftGroupsOrder[nextLeftGroupsOrderIdx] = temp;
                    }
                    // Decrement the number of unprocessed groups.
                    lastLeftGroupsOrderIdx--;
                }
            }

            // Convert password characters into a string and return the result.
            return new String(password);
        }


        public static string LeerFichero(string rutaFichero)
        {

            string texto = "";

            System.IO.StreamReader sr = new System.IO.StreamReader(rutaFichero);
            texto = sr.ReadToEnd();
            sr.Close();

            return texto;
        }

        public static void EscribirFichero(string rutaFichero, string texto)
        {
            EscribirFichero(rutaFichero, texto, true);
        }

        public static void EscribirFichero(string rutaFichero, string texto, bool concatenar)
        {
            System.IO.StreamWriter sw = new System.IO.StreamWriter(rutaFichero, concatenar);
            sw.WriteLine(texto);
            sw.Close();
        }

        public static void CrearFichero(string rutaFichero, string texto)
        {
            if (!File.Exists(rutaFichero))
            {
                FileStream fs = File.Create(rutaFichero);
                fs.Close();
            }

            EscribirFichero(rutaFichero, texto);
        }



    }
}
